      SUBROUTINE ROT123(KAXIS1,ANG1,KAXIS2,ANG2,KAXIS3,ANG3,RMAT,LUERR,
     1                  IERR)
      IMPLICIT REAL*8 (A-H,O-Z)
C
C  ROT123 COMPUTES A MATRIX, RMAT, THAT REFLECTS A SEQUENCE OF 0, 1, 2,
C  OR 3 ROTATIONS OF A COORDINATE SYSTEM ABOUT ITS OWN AXES. RMAT
C  TRANSFORMS COORDINATES FROM THE PRE-ROTATION COORDINATE SYSTEM TO
C  THOSE IN THE POST-ROTATION ONE(SEE THE RMAT ENTRY IN THE CALLING
C  SEQUENCE DESCRIPTION BELOW).
C
C  AN OBJECT HAS DIFFERENT COORDINATE VALUES IN DIFFERENT SYSTEMS. RMAT
C  IS USED TO TRANSFORM COORDINATE VALUES FROM ONE SYSTEM TO ANOTHER.
C  THE OBJECT ITSELF DOES NOT MOVE.
C
C  THE TERM ROTATION REFERS TO ROTATIONS THAT THE STARTING COORDINATE
C  SYSTEM WOULD UNDERGO IF ITS X/Y/Z AXES WERE TO BE ALIGNED WITH THOSE
C  OF THE FINAL SYSTEM.
C
C  EXAMPLES OF USES:
C
C     RMAT TRANSFORMS THE COORDINATES OF A STAR'S POSITION FROM MEAN
C     OF 1950.0 EQUATORIAL COORDINATE SYSTEM TO MEAN OF 1950.0 ECLIPTIC
C     COORDINATE SYSTEM. THE ROTATION IS ABOUT THE 1950.0'S X-AXIS. THE
C     STAR'S POSITION DOES NOT CHANGE, BUT THE COORDINATES DESCRIBING IT
C     CHANGE WHEN THE COORDINATE SYSTEM IS CHANGED.
C 
C     RMAT TRANSFORMS THE COORDINATES OF A STAR'S POSITION FROM
C     S/C-FIXED COORDINATES BEFORE A S/C ROLL, PITCH, YAW MANEUVER TO
C     THE S/C FIXED COORDINATES AFTER THE MANEUVER. THE STAR'S POSITION
C     DOES NOT CHANGE, BUT THE S/C-FIXED COORDINATES DESCRIBING IT
C     CHANGE WHEN THE S/C AXES CHANGE DIRECTION.
C
C     AT A GIVEN INSTANT, RMAT TRANSFORMS THE COORDINATES OF AN EARTH
C     SURFACE POSITION FROM EARTH-FIXED TO INERTIAL COORDINATES. THE
C     ROTATION IS ABOUT THE EARTH Z-AXIS. THE POSITION DOES NOT MOVE,
C     BUT THE X,Y,Z COORDINATES DESCRIBING IT CHANGE WHEN THE
C     COORDINATE SYSTEM IS CHANGED.
C
C  IF ROT1, ROT2, ROT3 ARE THE ROTATION MATRICES FOR THE FIRST, SECOND,
C  AND THIRD ROTATIONS, RESPECTIVELY, THEN
C
C     RMAT = ROT3 * ROT2 * ROT1
C
C  KAXISx ASSIGNMENTS:
C
C             KAXISx = 0, NO ROTATION. EQUIVALENT TO 0.0 ROTATION ANGLE.
C             KAXISx = 1, ROLL ABOUT X-AXIS.
C                         ANGx POSITIVE FROM +Y TOWARD +Z. 
C             KAXISx = 2, PITCH ABOUT Y-AXIS.
C                         ANGx POSITIVE FROM +Z TOWARD +X.
C             KAXISx = 3, YAW ABOUT Z-AXIS.
C                         ANGx POSITIVE FROM +X TOWARD +Y.
C             KAXISx = OTHERWISE, ERROR CONDITION.
C 
C             EXAMPLE:  KAXIS1=3, KAXIS2=1, KAXIS3=2 MEANS THAT THE
C                       FIRST ROTATION IS ABOUT THE Z-AXIS, THE SECOND 
C                       IS ABOUT THE X-AXIS, AND THE THIRD IS ABOUT THE
C                       Y-AXIS.
C
C      KAXISx VALUES MAY REPEAT THEMSELVES. EXAMPLES OF VALID INPUTS:
C
C              KAXIS1=2, KAXIS2=3, KAXIS3=2 
C              KAXIS1=3, KAXIS2=3, KAXIS3=3 
C              KAXIS1=0, KAXIS2=1, KAXIS3=0 
C              KAXIS1=2, KAXIS2=2, KAXIS3=2
C
C  VARIABLE  DIM  TYPE  I/O  DESCRIPTION
C  --------  ---  ----  ---  -----------
C
C  KAXIS1     1    I*4   I   AXIS NUMBER ABOUT WHICH THE FIRST ROTATION
C                            WILL OCCUR.
C
C  ANG1       1    R*8   I   ROTATION ANGLE CORRESPONDING TO KAXIS1. 
C                            IN RADIANS. IGNORED IF KAXIS1 = 0.
C
C  KAXIS2     1    I*4   I   AXIS NUMBER ABOUT WHICH THE SECOND ROTATION
C                            WILL OCCUR. THE SECOND AXIS MAY HAVE BEEN
C                            REPOSITIONED BY THE FIRST ROTATION.
C
C  ANG2       1    R*8   I   ROTATION ANGLE CORRESPONDING TO KAXIS2.
C                            IN RADIANS. IGNORED IF KAXIS2 = 0.
C
C  KAXIS3     1    I*4   I   AXIS NUMBER ABOUT WHICH THE THIRD ROTATION
C                            WILL OCCUR. THE THIRD AXIS MAY HAVE BEEN
C                            REPOSITIONED BY THE FIRST TWO ROTATIONS.
C
C  ANG3       1    R*8   I   ROTATION ANGLE CORRESPONDING TO KAXIS3.
C                            IN RADIANS. IGNORED IF KAXIS3 = 0.
C
C  RMAT      3,3   R*8   O   ROTATION MATRIX THAT TRANSFORMS COORDINATES
C                            FROM ONE SYSTEM TO ANOTHER.
C
C                            A VECTOR WHICH DOES NOT MOVE WITH THE
C                            ROTATIONS WILL HAVE COORDINATES 
C                            [V1(1),V1(2),V1(3)] BEFORE THE ROTATION 
C                            AND COORDINATES [V2(1),V2(2),V2(3)] AFTER 
C                            THE ROTATION. THE RELATIONSHIP IS:
C
C                               V2(I) = RMAT(I,J) * V1(J), SUMMING ON J.
C
C  LUERR      1    I*4   I   FORTRAN UNIT NUMBER FOR ERROR MESSAGES.
C                            PROGRAM CHECKS FOR INVALID KAXIS VALUES.
C                            LUERR = 0 MEANS NO ERROR MESSAGES POSSIBLE.
C
C  IERR       1    I*4   O   ERROR RETURN FLAG.
C                            = 0, NO ERROR.   =1, ERROR.
C
C***********************************************************************
C
C  BY C PETRUZZO, 2/83.
C       MODIFIED..... 4/85. CJP. COMMENT MODS, NO CODE MODS.
C
C***********************************************************************
C
      REAL*8 DEGRAD/ 57.29577951308232D0 /
      REAL*8 RMAT(3,3)
      REAL*8 AIDENT(3,3)/1.D0,3*0.D0,1.D0,3*0.D0,1.D0/
      REAL*8 ROT1AX(3,3),RSOFAR(3,3)
      INTEGER KAXIS(3),NERR/0/
      REAL*8 ANGVALS(3)
C
      IERR=0
C
C  LOAD KAXIS AND ANGVALS ARRAYS.
      KAXIS(1) = KAXIS1
      ANGVALS(1) = ANG1
      KAXIS(2) = KAXIS2
      ANGVALS(2) = ANG2
      KAXIS(3) = KAXIS3
      ANGVALS(3) = ANG3
C
C  SET RSOFAR TO THE IDENTITY MATRIX.
      CALL MTXEQL(AIDENT,RSOFAR,3,3)
C
C  ROTATE ABOUT EACH AXIS. MAY BE REPETITIONS.
      DO 100 IAX=1,3
      KAXNOW=KAXIS(IAX)
      IF(KAXNOW.EQ.0) GO TO 100
      ANGNOW=ANGVALS(IAX)
      IF(ANGNOW.EQ.0.D0) GO TO 100
C
C  ERROR CHECK.
      IF(KAXNOW.LT.0 .OR. KAXNOW.GT.3) THEN
        CALL MESAGE(1,NERR,20,0,1,1,LUERR,
     1     'ERROR IN ROT123. INVALID AXIS FLAG. ZERO ROTATION.')
        CALL MTXEQL(AIDENT,RSOFAR,3,3)
        IERR=1
        GO TO 110
        END IF
C
C  INITIALIZE FOR THE CURRENT AXIS.
      COSANG = DCOS(ANGNOW)
      SINANG = DSIN(ANGNOW)
      CALL MTXSETR8(ROT1AX,0.D0,3,3)   ! ZERO IT OUT.
C
      IF(KAXNOW.EQ.1) THEN
C       ROTATING ABOUT X-AXIS.
        ROT1AX(1,1)=1.D0
        ROT1AX(2,2)=COSANG
        ROT1AX(3,3)=COSANG
        ROT1AX(2,3)=SINANG
        ROT1AX(3,2)=-SINANG
        GO TO 150
        END IF
C
      IF(KAXNOW.EQ.2) THEN
C       ROTATING ABOUT Y-AXIS.
        ROT1AX(2,2)=1.D0
        ROT1AX(1,1)=COSANG
        ROT1AX(3,3)=COSANG
        ROT1AX(1,3)=-SINANG
        ROT1AX(3,1)=SINANG
        GO TO 150
        END IF
C
      IF(KAXNOW.EQ.3) THEN
C       ROTATING ABOUT Z-AXIS.
        ROT1AX(3,3)=1.D0
        ROT1AX(1,1)=COSANG
        ROT1AX(2,2)=COSANG
        ROT1AX(1,2)=SINANG
        ROT1AX(2,1)=-SINANG
        GO TO 150
        END IF
C
  150 CONTINUE
C
C  ROTATE(MULTIPLY) THE CURRENT RSOFAR ROTATION MATRIX BY THE MATRIX 
C  JUST COMPUTED, AND REPLACE RSOFAR WITH THE PRODUCT.
      CALL MTXMUL33(1,ROT1AX,RSOFAR,RSOFAR)
C
  100 CONTINUE
  110 CONTINUE
C
C  NOW LOAD RSOFAR INTO RMAT FOR RETURN TO CALLER.
      CALL MTXEQL(RSOFAR,RMAT,3,3)
C
      RETURN
      END
